/**
 * Copyright (C) 2010-2011 J.W.Marsden
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 **/
package cc.plural.jsonij.marshal.codec;

import cc.plural.jsonij.JSON;
import cc.plural.jsonij.Value;
import cc.plural.jsonij.marshal.JSONCodec;

/**
 * JSON codec implementation for java.util.Date. Encodes a java.util.Date instance
 * into a JSON Object with two attributes,
 *
 * <ol>
 *  <li>$type - The JSON String "java.util.Date"</li>
 *  <li>time - The value of getTime() from the java.util.Date</li>
 * </ol>
 *
 * @author openecho
 */
public class DateJSONCodec<D extends java.util.Date> extends JSONCodec<D> {

    /**
     * Helper method to create the specific internalType of the DateJSONCodec. This is
     * required to circumvent a short coming of Java Generics. Simply return a
     * new instance of the codec class with the generic internalType specified.
     * @return DateJSONCodec<java.util.Date> instance.
     */
    @Override
    public DateJSONCodec<? extends java.util.Date> createInstance() {
        return new DateJSONCodec<java.util.Date>();
    }

    /**
     * The encode method for the DateJSONCodec.
     * @param d Accepts any class D that extends java.util.Date
     * @return Value Object for the java.util.Date that is passed.
     */
    @Override
    public Value encode(D d) {
        JSON.Object<JSON.String, Value> object = new JSON.Object<JSON.String, Value>();
        object.put(new JSON.String("time"), new JSON.Numeric(d.getTime()));
        return object;
    }

    /**
     * The decode method for the DateJSONCodec.
     * @param value The JSON Value to be decoded.
     * @return D that extends java.util.Date representing the passed JSON Value
     */
    @Override
    public D decode(Value value) {
        if(value.getValueType() == Value.TYPE.OBJECT && value.has("time")) {
            return (D) new java.util.Date(value.get("time").getInt());
        } else {
            throw new UnsupportedOperationException("Incorrect Value Type.");
        }
    }
}
